package com.gengzp.rpc.config;

import io.lettuce.core.ClientOptions;
import io.lettuce.core.SocketOptions;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.connection.RedisStandaloneConfiguration;
import org.springframework.data.redis.connection.lettuce.LettuceClientConfiguration;
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.connection.lettuce.LettucePoolingClientConfiguration;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.RedisSerializer;

import java.time.Duration;

/**
 * @ClassName RpcRedisConfig
 * @Description rpc远程调用框架redis连接配置类
 * @Author gengzp
 * @Date 2025/8/11 19:51
 */
@Configuration
public class RpcRedisConfig {

    /**
     * redis地址
     */
    @Value("${spring.data.redis.host}")
    private String REDIS_HOST;

    /**
     * redis端口
     */
    @Value("${spring.data.redis.port}")
    private int REDIS_PORT;

    /**
     * redis连接密码
     */
    @Value("${spring.data.redis.password}")
    private String REDIS_PASSWORD;

    /**
     * redis使用数据库
     */
    @Value("${spring.data.redis.database}")
    private int REDIS_DATABASE;

    /**
     * lettuce 连接超时时间
     */
    @Value("${spring.data.redis.timeout}")
    private int REDIS_TIMEOUT;

    /**
     * redis连接工厂配置, 读取yaml文件中的配置信息
     */
    @Bean
    public RedisConnectionFactory rpcRedisConnectionFactory() {
        // 创建 Redis 单实例配置
        RedisStandaloneConfiguration config = new RedisStandaloneConfiguration(REDIS_HOST, REDIS_PORT);
        config.setPassword(REDIS_PASSWORD);
        config.setDatabase(REDIS_DATABASE);

        // 配置 Lettuce 客户端选项
        SocketOptions socketOptions = SocketOptions.builder()
                .connectTimeout(Duration.ofSeconds(REDIS_TIMEOUT))
                .build();
        ClientOptions clientOptions = ClientOptions.builder()
                .socketOptions(socketOptions)
                .build();

        // 创建 Lettuce 客户端配置
        LettuceClientConfiguration clientConfig = LettucePoolingClientConfiguration.builder()
                .clientOptions(clientOptions)
                .build();

        // 创建并返回 Lettuce 连接工厂
        return new LettuceConnectionFactory(config, clientConfig);
    }

    /**
     * 自定义redis模板, 替原来的 RedisTemplate<Object, Object>
     */
    @Bean
    public RedisTemplate<String, Object> rpcRedisTemplate(RedisConnectionFactory rpcRedisConnectionFactory) {
        //创建RedisTemplate对象
        RedisTemplate<String, Object> template = new RedisTemplate<>();
        //设置连接工厂
        template.setConnectionFactory(rpcRedisConnectionFactory);
        //创建json序列化工具
        GenericJackson2JsonRedisSerializer jsonRedisSerializer = new GenericJackson2JsonRedisSerializer();
        //设置key的序列化为String
        template.setKeySerializer(RedisSerializer.string());
        template.setHashKeySerializer(RedisSerializer.string());
        //设置value的序列化
        template.setValueSerializer(jsonRedisSerializer);
        template.setHashValueSerializer(jsonRedisSerializer);
        //返回
        return template;
    }

}
